<template>
  <div class="select">
    <Select v-model:value="selectValue" :disabled="disabledValue" style="width: 100%" :placeholder="placeholder"
      ref="orgSelect" :filter="filter" :options="options" :fieldNames="fieldNames" :filter-option="filterOption"
      :size="size" :dropdownClassName="className" show-search :allowClear="isAllowClears" @change="handleChange"
      :maxTagCount="2" :mode="mode">
      <template #dropdownRender="{ menuNode: menu }">
        <div style="
            display: flex;
            align-items: center;
            justify-content: center;
            width: 100%;
            height: 100px;
          " v-if="isLoading">
          <a-spin />
        </div>
        <div style="width: 100%; height: 100px; line-height: 100px; text-align: center" v-else-if="!options">
          <!-- <template> -->
          暂无数据
          <!-- </template> -->
        </div>
        <!--显示结果-->
        <!--v-nodes必须要写在最后面,这个代表要渲染的下拉列表数据-->
        <div v-else>
          <v-nodes :vnodes="menu" />
        </div>
      </template>
    </Select>
  </div>
</template>

<script lang="ts">
import { defineComponent, ref, watch, unref } from 'vue';
import { defHttp } from '@/utils/http/axios';
import { Select } from 'ant-design-vue';

type TypeList =
  | 'org'
  | 'role'
  | 'maps'
  | 'lines'
  | 'groups'
  | 'locationGroups'
  | 'personList'
  | 'dictList'
  | 'binderConfig'
  | 'bed'
  | 'warnList';

enum typeFunc {
  org = 'Organizations/Select', //机构
  role = 'Roles/select',
  maps = 'Maps',
  lines = 'BizPatrolWay/Select',
  groups = 'BizPatrolGroup/Select',
  locationGroups = '/BinderGroup/NoTree',
  area = 'areas',
  unBindList = 'Terminal/UnBindMany',
  personList = 'binder-devices/All',
  member = '',
  alarmRulesbyId = 'Warnings/AlarmRuleMinimalsByDevId',
  alarmRules = 'Warnings/AlarmRuleMinimals',
  dictList = 'key-values/Trees/AllByParentCode',
  trackList = 'binder-devices',
  bed = "/Beds/Null",
  binderConfig = "/key-values/SelectLink",
  warnList = "Warnings/WarnType",
  dictListPatrol = 'key-values/Select/PATROL_WARN_TYPE',
  enegy = 'key-values/EnableTreesHasSelf',
}

export default defineComponent({
  name: 'RwSelect',
  components: {
    VNodes: (_, { attrs }) => {
      return attrs.vnodes;
    },
    Select,
  },
  props: {
    className: {
      type: String,
      default: '',
    },
    defaultValue: {
      type: String,
      default: '',
    },
    customKey: {
      type: String,
      default: '',
    },
    type: {
      type: String,
      default: 'org',
    },
    label: {
      type: String,
      default: 'name',
    },
    keyValue: {
      type: String,
      default: 'id',
    },
    value: {
      type: String,
      default: '',
    },
    size: {
      type: String,
      default: 'small',
    },
    placeholder: {
      type: String,
      default: '请选择',
    },
    watchParams: {
      type: String || Array,
      default: '',
    },
    disabled: {
      type: Boolean,
      default: false,
    },
    isAllowClears: {
      type: Boolean,
      default: true,
    },
    filter: {
      type: Boolean,
      default: true,
    },
    afterEcah: {
      type: Function,
    },
    beforeEach: {
      type: Function,
    },
    changeHandler: {
      type: Function,
    },
    xhrParams: {
      type: Object,
      default: () => {
        return {
          data: 'entities',
          pageIndex: 1,
          pageSize: 100,
        };
      },
    },
    mode: {
      type: String,
      default: 'Middle',
    },
  },
  setup(props, context) {
    const isLoading = ref(true);
    const selectValue = ref<string | number | Array<string>>();
    let {
      type,
      xhrParams,
      label,
      keyValue,
      watchParams,
      disabled,
      afterEcah,
      beforeEach,
      changeHandler,
      isAllowClears,
      customKey,
      mode,
      defaultValue,
      filter,
      value,
    } = props;
    const options = ref([]);
    const disabledValue = ref(disabled);
    const orgSelect = ref(null);
    const fieldNames = {
      label,
      value: keyValue,
    };
    watch(
      () => props.value,
      (n) => {

        if (n instanceof Array) {
          selectValue.value = n;
        } else if (mode === 'multiple' && !n) {
          selectValue.value = [];
        } else if (n) {
          selectValue.value = n + '';
        } else {
          selectValue.value = ' ';
        }
      },
    );
    watch(
      () => props.disabled,
      (n) => {
        disabledValue.value = n;
      },
    );
    if (watchParams) {

      //当进行多个监听的时候只监听这个对象，不监听所有的key
      if (Array.isArray(watchParams)) {
        // watchParams.forEach((item: any) => {
        watch(
          () => props.xhrParams,
          (n) => {
            // console.log("sdfsdfsaf", n)
            if (xhrParams === n) return false
            xhrParams = n;
            getselectList(type as TypeList);
          },
          {
            // deep: true,
          },
        );
        // });
      } else {
        watch(
          () => props.xhrParams[watchParams],
          (n) => {
            if (n) {
              xhrParams[watchParams] = n;
              if (!typeFunc[type]) {
                getselectList(type as TypeList, n);
                return;
              }
              getselectList(type as TypeList);
            }
          },
          // {
          //   deep: true,
          // },
        );
      }
    }

    const handleChange = (value: string) => {
      let r = options.value.find((item) => {
        return item[keyValue] == value;
      });
      context.emit('input', value, r);
      context.emit('change', value, r);
      context.emit('customChange', value, r);
      context.emit('changeKey', value, customKey + 'field', customKey);
      context.emit('changeNative', r);
      changeHandler && changeHandler(value || {}, unref(options));
    };

    // 根据type不同调用不同的接口
    const getselectList = (type: TypeList, n?: string) => {
      let url = n || typeFunc[type];
      setTimeout(() => {
        //当选中标签的时候，监听的组件会调用接口，解决下拉框在关闭的时候的抖动问题
        isLoading.value = true;
      }, 300);
      if (xhrParams.customKey) {
        xhrParams[xhrParams.customKey] = xhrParams[xhrParams.customKey + customKey];
        delete xhrParams[xhrParams.customKey + customKey];
      }
      if (xhrParams.customKey && !xhrParams[xhrParams.customKey]) {
        return false;
      }
      defHttp
        .get({ url, params: xhrParams })
        .then((res) => {
          if (xhrParams.data == 'entities') {
            formatList(res.data.entities);
          } else {
            formatList(res.data);
          }
          // 如果有回显的值  就不能给默认值
          if (defaultValue && res.data.length > 0 && !value) {
            selectValue.value = res.data[0][keyValue] || res.data[0][defaultValue];
            context.emit('change', selectValue.value, res.data[0]);
          }
          context.emit('loadList', options.value);
        })
        .finally(() => {
          setTimeout(() => {
            isLoading.value = false;
          }, 300);
        });
    };
    const formatList = (list): [] => {
      if (!list) return [];
      if (typeof afterEcah == 'function') {
        options.value = afterEcah(list);
      } else {
        options.value = list;
      }
      options.value = options.value || [];
    };
    const filterOption = (input: string, option: any) => {
      if (!filter) return;
      let name = option[label];
      return name.toLowerCase().indexOf(input.toLowerCase()) >= 0;
    };
    if (xhrParams.value) selectValue.value = xhrParams.value;
    getselectList(type as TypeList);
    return {
      selectValue,
      fieldNames,
      options,
      orgSelect,
      disabled,
      isAllowClears,
      disabledValue,
      filter,
      handleChange,
      filterOption,
      isLoading,
    };
  },
});
</script>

<style>
.select {
  width: 100%;
}
</style>
